version = "0.0.1-pre"
dependencies = [
"curl 0.0.1 (git+https://github.com/alexcrichton/curl-rust?ref=bundle#1d43e08f629dc22ffbc99d7ea8e97dfc7ab0b91a)",
- "docopt 0.6.4 (git+https://github.com/docopt/docopt.rs#db3abbb1d55aec986daefcf4b6131a61ff78513c)",
- "docopt_macros 0.6.4 (git+https://github.com/docopt/docopt.rs#db3abbb1d55aec986daefcf4b6131a61ff78513c)",
+ "docopt 0.6.4 (git+https://github.com/docopt/docopt.rs#4544a9f422b115c2ffef4ee9baf27ceb07c34602)",
"flate2 0.0.1 (git+https://github.com/alexcrichton/flate2-rs#68971ae77a523c7ec3f19b4bcd195f76291ea390)",
"git2 0.0.1 (git+https://github.com/alexcrichton/git2-rs#c01b0b279470552c48cf7f902ae5baf132df0a6d)",
"glob 0.0.1 (git+https://github.com/rust-lang/glob#27338cbd4736d3c8146294fc090c6f8f06c32d72)",
[[package]]
name = "docopt"
version = "0.6.4"
-source = "git+https://github.com/docopt/docopt.rs#db3abbb1d55aec986daefcf4b6131a61ff78513c"
-
-[[package]]
-name = "docopt_macros"
-version = "0.6.4"
-source = "git+https://github.com/docopt/docopt.rs#db3abbb1d55aec986daefcf4b6131a61ff78513c"
-dependencies = [
- "docopt 0.6.4 (git+https://github.com/docopt/docopt.rs#db3abbb1d55aec986daefcf4b6131a61ff78513c)",
-]
+source = "git+https://github.com/docopt/docopt.rs#4544a9f422b115c2ffef4ee9baf27ceb07c34602"
[[package]]
name = "encoding"
[dependencies.docopt]
git = "https://github.com/docopt/docopt.rs"
-[dependencies.docopt_macros]
-git = "https://github.com/docopt/docopt.rs"
-
[dependencies.toml]
git = "https://github.com/alexcrichton/toml-rs"
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError, CargoError};
use cargo::util::important_paths::{find_root_manifest_for_cwd};
-use docopt;
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_no_run: bool,
+ flag_package: Option<String>,
+ flag_jobs: Option<uint>,
+ flag_features: Vec<String>,
+ flag_no_default_features: bool,
+ flag_target: Option<String>,
+ flag_manifest_path: Option<String>,
+ flag_verbose: bool,
+ arg_args: Vec<String>,
+}
+
+pub const USAGE: &'static str = "
Execute all benchmarks of a local package
Usage:
which indicates which package should be benchmarked. If it is not given, then
the current package is benchmarked. For more information on SPEC and its format,
see the `cargo help pkgid` command.
-", flag_jobs: Option<uint>, flag_target: Option<String>,
- flag_manifest_path: Option<String>, flag_features: Vec<String>,
- flag_package: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
let root = try!(find_root_manifest_for_cwd(options.flag_manifest_path));
use cargo::ops;
use cargo::util::important_paths::{find_root_manifest_for_cwd};
use cargo::util::{CliResult, CliError};
-use docopt;
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_package: Option<String>,
+ flag_jobs: Option<uint>,
+ flag_features: Vec<String>,
+ flag_no_default_features: bool,
+ flag_target: Option<String>,
+ flag_manifest_path: Option<String>,
+ flag_verbose: bool,
+ flag_release: bool,
+}
+
+pub const USAGE: &'static str = "
Compile a local package and all of its dependencies
Usage:
which indicates which package should be built. If it is not given, then the
current package is built. For more information on SPEC and its format, see the
`cargo help pkgid` command.
-", flag_jobs: Option<uint>, flag_target: Option<String>,
- flag_manifest_path: Option<String>, flag_features: Vec<String>,
- flag_package: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
debug!("executing; cmd=cargo-build; args={}", os::args());
#![feature(phase, macro_rules)]
+#![deny(unused)]
extern crate serialize;
#[phase(plugin, link)] extern crate log;
extern crate cargo;
-extern crate docopt;
-#[phase(plugin)] extern crate docopt_macros;
use std::collections::TreeSet;
use std::os;
use std::io;
use std::io::fs::{mod, PathExtensions};
use std::io::process::{Command,InheritFd,ExitStatus,ExitSignal};
-use docopt::FlagParser;
use cargo::{execute_main_without_stdin, handle_error, shell};
use cargo::core::MultiShell;
use cargo::util::{CliError, CliResult};
-fn main() {
- execute_main_without_stdin(execute, true)
+#[deriving(Decodable)]
+struct Flags {
+ flag_list: bool,
+ flag_verbose: bool,
+ arg_command: String,
+ arg_args: Vec<String>,
}
-docopt!(Flags, "
+const USAGE: &'static str = "
Rust's package manager
Usage:
update Update dependencies listed in Cargo.lock
See 'cargo help <command>' for more information on a specific command.
-")
+";
+
+fn main() {
+ execute_main_without_stdin(execute, true, USAGE)
+}
macro_rules! each_subcommand( ($macro:ident) => ({
$macro!(bench)
let (mut args, command) = match flags.arg_command.as_slice() {
"" | "help" if flags.arg_args.len() == 0 => {
shell.set_verbose(true);
- let r = cargo::call_main_without_stdin(execute, shell,
+ let r = cargo::call_main_without_stdin(execute, shell, USAGE,
["-h".to_string()], false);
cargo::process_executed(r, shell);
return Ok(None)
mod $name;
shell.set_verbose(true);
let r = cargo::call_main_without_stdin($name::execute, shell,
+ $name::USAGE,
args.as_slice(),
false);
cargo::process_executed(r, shell);
use std::os;
-use docopt;
use cargo::ops;
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError};
use cargo::util::important_paths::{find_root_manifest_for_cwd};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_package: Option<String>,
+ flag_target: Option<String>,
+ flag_manifest_path: Option<String>,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Remove artifacts that cargo has generated in the past
Usage:
which indicates which package's artifacts should be cleaned out. If it is not
given, then all packages' artifacts are removed. For more information on SPEC
and its format, see the `cargo help pkgid` command.
-", flag_manifest_path: Option<String>, flag_package: Option<String>,
- flag_target: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
shell.set_verbose(options.flag_verbose);
use std::os;
use std::collections::HashMap;
-use docopt;
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError, config};
+#[deriving(Decodable)]
+struct ConfigForKeyFlags {
+ flag_human: bool,
+ flag_key: String,
+}
+
#[deriving(Encodable)]
struct ConfigOut {
values: HashMap<String, config::ConfigValue>
}
-docopt!(ConfigForKeyFlags, "
+pub const USAGE: &'static str = "
Usage:
cargo config-for-key --human --key=<key>
cargo config-for-key -h | --help
Options:
-h, --help Print this message
-")
+";
pub fn execute(args: ConfigForKeyFlags,
_: &mut MultiShell) -> CliResult<Option<ConfigOut>> {
use std::os;
use std::collections::HashMap;
-use docopt;
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError, config};
+#[deriving(Decodable)]
+struct ConfigListFlags {
+ flag_human: bool,
+}
+
#[deriving(Encodable)]
struct ConfigOut {
values: HashMap<String, config::ConfigValue>
}
-docopt!(ConfigListFlags, "
+pub const USAGE: &'static str = "
Usage:
cargo config-list --human
cargo config-list -h | --help
Options:
-h, --help Print this message
-")
+";
pub fn execute(args: ConfigListFlags,
_: &mut MultiShell) -> CliResult<Option<ConfigOut>> {
-use docopt;
-
use cargo::ops;
use cargo::core::{MultiShell};
use cargo::util::{CliResult, CliError};
use cargo::util::important_paths::{find_root_manifest_for_cwd};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_features: Vec<String>,
+ flag_jobs: Option<uint>,
+ flag_manifest_path: Option<String>,
+ flag_no_default_features: bool,
+ flag_no_deps: bool,
+ flag_open: bool,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Build a package's documentation
Usage:
By default the documentation for the local package and all dependencies is
built. The output is all placed in `target/doc` in rustdoc's usual format.
-", flag_jobs: Option<uint>,
- flag_manifest_path: Option<String>,
- flag_features: Vec<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
shell.set_verbose(options.flag_verbose);
-use docopt;
-
use cargo::ops;
use cargo::core::{MultiShell};
use cargo::util::{CliResult, CliError};
use cargo::util::important_paths::find_root_manifest_for_cwd;
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_manifest_path: Option<String>,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Fetch dependencies of a package from the network.
Usage:
If the lockfile is not available, then this is the equivalent of
`cargo generate-lockfile`. A lockfile is generated and dependencies are also
all updated.
-", flag_manifest_path: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
shell.set_verbose(options.flag_verbose);
use std::os;
-use docopt;
use cargo::ops;
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError};
use cargo::util::important_paths::find_root_manifest_for_cwd;
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_manifest_path: Option<String>,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Generate the lockfile for a project
Usage:
-h, --help Print this message
--manifest-path PATH Path to the manifest to generate a lockfile for
-v, --verbose Use verbose output
-", flag_manifest_path: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
debug!("executing; cmd=cargo-generate-lockfile; args={}", os::args());
-use docopt;
-
use cargo::core::MultiShell;
use cargo::core::source::{Source, SourceId};
use cargo::sources::git::{GitSource};
use cargo::util::{Config, CliResult, CliError, human, ToUrl};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_url: String,
+ flag_reference: String,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Usage:
cargo git-checkout [options] --url=URL --reference=REF
cargo git-checkout -h | --help
Options:
-h, --help Print this message
-v, --verbose Use verbose output
-")
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
+ shell.set_verbose(options.flag_verbose);
let Options { flag_url: url, flag_reference: reference, .. } = options;
let url = try!(url.as_slice().to_url().map_err(|e| {
-use docopt;
-
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options;
+
+pub const USAGE: &'static str = "
Get some help with a cargo command.
Usage:
Options:
-h, --help Print this message
-")
+";
pub fn execute(_: Options, _: &mut MultiShell) -> CliResult<Option<()>> {
// This is a dummy command just so that `cargo help help` works.
-use docopt;
-
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError, human, Require};
use cargo::util::important_paths::{find_root_manifest_for_cwd};
-docopt!(LocateProjectFlags, "
+#[deriving(Decodable)]
+struct LocateProjectFlags {
+ flag_manifest_path: Option<String>,
+}
+
+pub const USAGE: &'static str = "
Usage:
cargo locate-project [options]
Options:
--manifest-path PATH Path to the manifest to build benchmarks for
-h, --help Print this message
-", flag_manifest_path: Option<String>)
+";
#[deriving(Encodable)]
struct ProjectLocation {
use std::io;
-use docopt;
use cargo::ops;
use cargo::core::{MultiShell};
use cargo::sources::RegistrySource;
use cargo::util::{CliResult, CliError};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_host: Option<String>,
+ arg_token: Option<String>,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Save an api token from the registry locally
Usage:
--host HOST Host to set the token for
-v, --verbose Use verbose output
-", arg_token: Option<String>, flag_host: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
shell.set_verbose(options.flag_verbose);
use std::os;
-use docopt;
use cargo::ops;
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_verbose: bool,
+ flag_bin: bool,
+ flag_travis: bool,
+ flag_hg: bool,
+ flag_git: bool,
+ flag_no_git: bool,
+ arg_path: String,
+}
+
+pub const USAGE: &'static str = "
Create a new cargo package at <path>
Usage:
--travis Create a .travis.yml file
--bin Use a binary instead of a library template
-v, --verbose Use verbose output
-")
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
debug!("executing; cmd=cargo-new; args={}", os::args());
-use docopt;
use cargo::ops;
use cargo::core::{MultiShell};
use cargo::util::{CliResult, CliError};
use cargo::util::important_paths::find_root_manifest_for_cwd;
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_verbose: bool,
+ flag_manifest_path: Option<String>,
+}
+
+pub const USAGE: &'static str = "
Assemble a the local package into a distributable tarball
Usage:
--manifest-path PATH Path to the manifest to compile
-v, --verbose Use verbose output
-", flag_manifest_path: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
shell.set_verbose(options.flag_verbose);
-use docopt;
-
use cargo::ops;
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError};
use cargo::util::important_paths::{find_root_manifest_for_cwd};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_verbose: bool,
+ flag_manifest_path: Option<String>,
+ arg_spec: Option<String>,
+}
+
+pub const USAGE: &'static str = "
Print a fully qualified package specification
Usage:
crates.io/bar#foo:1.2.3 | foo | 1.2.3 | *://crates.io/bar
http://crates.io/foo#1.2.3 | foo | 1.2.3 | http://crates.io/foo
-", flag_manifest_path: Option<String>, arg_spec: Option<String>)
+";
pub fn execute(options: Options,
shell: &mut MultiShell) -> CliResult<Option<()>> {
-use docopt;
-
use cargo::core::{MultiShell, Package, Source};
use cargo::util::{CliResult, CliError};
use cargo::sources::{PathSource};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_manifest_path: String,
+}
+
+pub const USAGE: &'static str = "
Usage:
cargo read-manifest [options] --manifest-path=PATH
cargo read-manifest -h | --help
Options:
-h, --help Print this message
-v, --verbose Use verbose output
-")
+";
pub fn execute(options: Options, _: &mut MultiShell) -> CliResult<Option<Package>> {
let path = Path::new(options.flag_manifest_path.as_slice());
use std::io::process::ExitStatus;
-use docopt;
use cargo::ops;
use cargo::core::{MultiShell};
use cargo::util::{CliResult, CliError};
use cargo::util::important_paths::{find_root_manifest_for_cwd};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_jobs: Option<uint>,
+ flag_features: Vec<String>,
+ flag_no_default_features: bool,
+ flag_target: Option<String>,
+ flag_manifest_path: Option<String>,
+ flag_verbose: bool,
+ flag_release: bool,
+ arg_args: Vec<String>,
+}
+
+pub const USAGE: &'static str = "
Run the main binary of the local package (src/main.rs)
Usage:
-v, --verbose Use verbose output
All of the trailing arguments are passed as to the binary to run.
-", flag_jobs: Option<uint>, flag_target: Option<String>,
- flag_manifest_path: Option<String>, flag_features: Vec<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
shell.set_verbose(options.flag_verbose);
use std::io::process::ExitStatus;
-use docopt;
use cargo::ops;
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError, CargoError};
use cargo::util::important_paths::{find_root_manifest_for_cwd};
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ arg_args: Vec<String>,
+ flag_features: Vec<String>,
+ flag_jobs: Option<uint>,
+ flag_manifest_path: Option<String>,
+ flag_no_default_features: bool,
+ flag_no_run: bool,
+ flag_package: Option<String>,
+ flag_target: Option<String>,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Execute all unit and integration tests of a local package
Usage:
which indicates which package should be tested. If it is not given, then the
current package is tested. For more information on SPEC and its format, see the
`cargo help pkgid` command.
-", flag_jobs: Option<uint>, flag_target: Option<String>,
- flag_manifest_path: Option<String>, flag_features: Vec<String>,
- flag_package: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
let root = try!(find_root_manifest_for_cwd(options.flag_manifest_path));
use std::os;
-use docopt;
use cargo::ops;
use cargo::core::MultiShell;
use cargo::util::{CliResult, CliError};
use cargo::util::important_paths::find_root_manifest_for_cwd;
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ arg_spec: Option<String>,
+ flag_package: Option<String>,
+ flag_aggressive: bool,
+ flag_precise: Option<String>,
+ flag_manifest_path: Option<String>,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Update dependencies as recorded in the local lock file.
Usage:
updated.
For more information about package id specifications, see `cargo help pkgid`.
-", flag_manifest_path: Option<String>, arg_spec: Option<String>,
- flag_precise: Option<String>, flag_package: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
debug!("executing; cmd=cargo-update; args={}", os::args());
-use docopt;
-
use cargo::ops;
use cargo::core::{MultiShell};
use cargo::util::{CliResult, CliError};
use cargo::util::important_paths::find_root_manifest_for_cwd;
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options {
+ flag_host: Option<String>,
+ flag_token: Option<String>,
+ flag_manifest_path: Option<String>,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Upload a package to the registry
Usage:
--manifest-path PATH Path to the manifest to compile
-v, --verbose Use verbose output
-", flag_host: Option<String>, flag_token: Option<String>,
- flag_manifest_path: Option<String>)
+";
pub fn execute(options: Options, shell: &mut MultiShell) -> CliResult<Option<()>> {
shell.set_verbose(options.flag_verbose);
use std::collections::HashMap;
use std::io::File;
use std::os;
-use docopt;
use cargo::core::MultiShell;
use cargo::util::CliResult;
pub type Error = HashMap<String, String>;
-docopt!(Flags, "
+#[deriving(Decodable)]
+struct Flags {
+ flag_manifest_path: String,
+ flag_verbose: bool,
+}
+
+pub const USAGE: &'static str = "
Usage:
cargo verify-project [options] --manifest-path PATH
cargo verify-project -h | --help
-h, --help Print this message
--manifest-path PATH Path to the manifest to verify
-v, --verbose Use verbose output
-")
+";
pub fn execute(args: Flags,
shell: &mut MultiShell) -> CliResult<Option<Error>> {
use std::os;
-use docopt;
use cargo;
use cargo::core::MultiShell;
use cargo::util::CliResult;
-docopt!(Options, "
+#[deriving(Decodable)]
+struct Options;
+
+pub const USAGE: &'static str = "
Usage:
cargo version [options]
Options:
-h, --help Print this message
-v, --verbose Use verbose output
-")
+";
pub fn execute(_: Options, _: &mut MultiShell) -> CliResult<Option<()>> {
debug!("executing; cmd=cargo-version; args={}", os::args());
use std::hash;
use serialize::{Encodable, Encoder, Decodable, Decoder};
+use regex::Regex;
+
use util::{CargoResult, CargoError, short_hash, ToSemver};
use core::source::SourceId;
impl<E, D: Decoder<E>> Decodable<D, E> for PackageId {
fn decode(d: &mut D) -> Result<PackageId, E> {
let string: String = raw_try!(Decodable::decode(d));
- let regex = regex!(r"^([^ ]+) ([^ ]+) \(([^\)]+)\)$");
+ let regex = Regex::new(r"^([^ ]+) ([^ ]+) \(([^\)]+)\)$").unwrap();
let captures = regex.captures(string.as_slice()).expect("invalid serialized PackageId");
let name = captures.at(1);
use std::collections::hashmap::{HashMap, HashSet, Occupied, Vacant};
use std::fmt;
-use semver;
+use regex::Regex;
+use semver;
use serialize::{Encodable, Encoder, Decodable, Decoder};
use core::{PackageId, Registry, SourceId, Summary, Dependency};
impl<E, D: Decoder<E>> Decodable<D, E> for EncodablePackageId {
fn decode(d: &mut D) -> Result<EncodablePackageId, E> {
let string: String = raw_try!(Decodable::decode(d));
- let regex = regex!(r"^([^ ]+) ([^ ]+)(?: \(([^\)]+)\))?$");
+ let regex = Regex::new(r"^([^ ]+) ([^ ]+)(?: \(([^\)]+)\))?$").unwrap();
let captures = regex.captures(string.as_slice())
.expect("invalid serialized PackageId");
extern crate serialize;
extern crate term;
extern crate time;
-#[phase(plugin)] extern crate regex_macros;
#[phase(plugin, link)] extern crate log;
extern crate curl;
use std::io::stdio::{stdout_raw, stderr_raw};
use std::io::{mod, stdout, stderr};
use serialize::{Decoder, Encoder, Decodable, Encodable, json};
-use docopt::FlagParser;
use core::{Shell, MultiShell, ShellConfig};
use term::color::{BLACK};
impl<T: Decodable<json::Decoder, json::DecoderError>> RepresentsJSON for T {}
pub fn execute_main<'a,
- T: FlagParser,
+ T: Decodable<docopt::Decoder, docopt::Error>,
U: RepresentsJSON,
V: Encodable<json::Encoder<'a>, io::IoError>>(
exec: fn(T, U, &mut MultiShell) -> CliResult<Option<V>>,
- options_first: bool) {
- // see comments below
- off_the_main_thread(proc() {
- process::<V>(|rest, shell| call_main(exec, shell, rest, options_first));
- });
+ options_first: bool,
+ usage: &str) {
+ process::<V>(|rest, shell| call_main(exec, shell, usage, rest, options_first));
}
pub fn call_main<'a,
- T: FlagParser,
+ T: Decodable<docopt::Decoder, docopt::Error>,
U: RepresentsJSON,
V: Encodable<json::Encoder<'a>, io::IoError>>(
exec: fn(T, U, &mut MultiShell) -> CliResult<Option<V>>,
shell: &mut MultiShell,
+ usage: &str,
args: &[String],
options_first: bool) -> CliResult<Option<V>> {
- let flags = try!(flags_from_args::<T>(args, options_first));
+ let flags = try!(flags_from_args::<T>(usage, args, options_first));
let json = try!(json_from_stdin::<U>());
exec(flags, json, shell)
}
pub fn execute_main_without_stdin<'a,
- T: FlagParser,
+ T: Decodable<docopt::Decoder, docopt::Error>,
V: Encodable<json::Encoder<'a>, io::IoError>>(
exec: fn(T, &mut MultiShell) -> CliResult<Option<V>>,
- options_first: bool) {
- // see comments below
- off_the_main_thread(proc() {
- process::<V>(|rest, shell| call_main_without_stdin(exec, shell, rest,
- options_first));
- });
+ options_first: bool,
+ usage: &str) {
+ process::<V>(|rest, shell| call_main_without_stdin(exec, shell, usage, rest,
+ options_first));
}
pub fn call_main_without_stdin<'a,
- T: FlagParser,
+ T: Decodable<docopt::Decoder, docopt::Error>,
V: Encodable<json::Encoder<'a>, io::IoError>>(
exec: fn(T, &mut MultiShell) -> CliResult<Option<V>>,
shell: &mut MultiShell,
+ usage: &str,
args: &[String],
options_first: bool) -> CliResult<Option<V>> {
- let flags = try!(flags_from_args::<T>(args, options_first));
+ let flags = try!(flags_from_args::<T>(usage, args, options_first));
exec(flags, shell)
}
})
}
-fn flags_from_args<T: FlagParser>(args: &[String],
- options_first: bool) -> CliResult<T> {
+fn flags_from_args<'a, T>(usage: &str, args: &[String],
+ options_first: bool) -> CliResult<T>
+ where T: Decodable<docopt::Decoder, docopt::Error> {
let args = args.iter().map(|a| a.as_slice()).collect::<Vec<&str>>();
let config = docopt::Config {
options_first: options_first,
help: true,
version: Some(version()),
};
- FlagParser::parse_args(config, args.as_slice()).map_err(|e| {
+ let value_map = try!(docopt::docopt_args(config, args.as_slice(),
+ usage).map_err(|e| {
+ let code = if e.fatal() {1} else {0};
+ CliError::from_error(e, code)
+ }));
+ value_map.decode().map_err(|e| {
let code = if e.fatal() {1} else {0};
CliError::from_error(e, code)
})
CliError::new("Could not process standard in as input", 1)
})
}
-
-// Seems curious to run cargo off the main thread, right? Well do I have a story
-// for you. Turns out rustdoc does a similar thing, and already has a good
-// explanation [1] though, so I'll just point you over there.
-//
-// [1]: https://github.com/rust-lang/rust/blob/85fd37f/src/librustdoc/lib.rs#L92-L122
-fn off_the_main_thread(p: proc():Send) {
- let (tx, rx) = channel();
- spawn(proc() { p(); tx.send(()); });
- if rx.recv_opt().is_err() {
- std::os::set_exit_status(std::rt::DEFAULT_ERROR_CODE);
- }
-}